﻿using System;
using NLog;
using NLog.Targets;

namespace Quebec.Logging
{
    [Target("WADLogTable")]
    public sealed class AzureLogger : TargetWithLayout
    {
        public AzureLogger()
        {
        }

        protected override void Write(LogEventInfo logEvent)
        {
            string logMessage = this.Layout.Render(logEvent);
            System.Diagnostics.TraceLevel level = GetTraceLevel(logEvent.Level);

            LogMessageWithAzure(logMessage, level);
        }

        /// <summary>
        /// Gets the TraceLevel from the LogLevel.
        /// </summary>
        /// <param name="logLevel">The log level.</param>
        /// <returns></returns>
        private System.Diagnostics.TraceLevel GetTraceLevel(LogLevel logLevel)
        {
            if (logLevel == LogLevel.Debug)
            {
                return System.Diagnostics.TraceLevel.Verbose;
            }
            else if (logLevel == LogLevel.Error)
            {
                return System.Diagnostics.TraceLevel.Error;
            }
            else if (logLevel == LogLevel.Fatal)
            {
                return System.Diagnostics.TraceLevel.Error;
            }
            else if (logLevel == LogLevel.Info)
            {
                return System.Diagnostics.TraceLevel.Info;
            }
            else if (logLevel == LogLevel.Trace)
            {
                return System.Diagnostics.TraceLevel.Verbose;
            }
            else if (logLevel == LogLevel.Warn)
            {
                return System.Diagnostics.TraceLevel.Warning;
            }
            else if (logLevel == LogLevel.Off)
            {
                return System.Diagnostics.TraceLevel.Off;
            }

            throw new ArgumentOutOfRangeException("logLevel");
        }

        /// <summary>
        /// Logs the message with azure.
        /// </summary>
        /// <param name="logMessage">The log message.</param>
        /// <param name="logLevel">The log level.</param>
        private void LogMessageWithAzure(string logMessage, System.Diagnostics.TraceLevel traceLevel)
        {
            // we could build a new table writing structure here. For our purposes, we will just write to WADLogTable
            var traceListener = new Microsoft.WindowsAzure.Diagnostics.DiagnosticMonitorTraceListener();

            System.Diagnostics.Trace.Listeners.Add(traceListener);
            traceListener.WriteLine(logMessage, traceLevel.ToString());
            System.Diagnostics.Trace.Listeners.Remove(traceListener);
        }
    }
}
